# coding=utf-8
import copy
import os
import re
import sys
import traceback

import pandas
import pandas as pd
from loguru import logger

from models.stock_model import StockNumber, DayInfo
from mylib.mycsv import sort_csv2
from update_sh import get_bkd_today, get_sh_down_date


def get_3down_len(today_date, sn, N):
    """
    获取最近N次下跌，连续下跌天数计数
    """
    sc = f'stocks/{sn.ts_code}.csv'
    if not os.path.exists(sc):
        return None, None, None, None, None, None
    df = pandas.read_csv(sc)
    today_d = None
    start_row = 0
    down_times = 0
    vol2times = 0
    add_index = 0
    result_arr = []
    for row in df.index:
        d = DayInfo(sn, df.loc[row])
        if d.trade_date_str > today_date:
            continue
        if today_d is None:
            today_d = copy.deepcopy(d)
            start_row = row
            if today_d.trade_date_str != today_date:
                return None, None, None, None, None, None
        if result_arr:
            if d.vol * 2 < result_arr[-1].vol:
                vol2times += 1
        result_arr.append(d)

        if (row - start_row) == down_times and d.pct_chg <= 0:
            down_times += 1

        try:
            di_n = [DayInfo(sn, df.loc[i]) for i in range(start_row + add_index, start_row + add_index + N)]
            di_n_high = [di.high for di in di_n]
            # 找到最近一次N日顶点
            if max(di_n_high) == di_n_high[0]:
                break
            add_index += 1
        except Exception as e:
            return None, None, None, None, None, None

    res = re.findall('stocks/(.*).csv', sc)
    link_code_arr = res[0].split('.')
    link_code = f'{link_code_arr[1]}{link_code_arr[0]}'
    hyperlink = f'"https://xueqiu.com/S/{link_code}"'
    date_arr_hyp = f'=HYPERLINK({hyperlink})'
    print(today_date, sn.name, hyperlink)
    if not result_arr:
        return None, None, None, None, None, None
    di_result_high = [di.high for di in result_arr]
    if max(di_result_high) < max(di_result_high):
        return None, None, None, None, None, None
    di_result_low = [di.low for di in result_arr]
    # 今日不为最低价的不要
    if min(di_result_low) != di_result_low[0]:
        return None, None, None, None, None, None
    if vol2times > 0:
        return None, None, None, None, None, None
    all_down = round((max(di_result_high) - min(di_result_low)) / (max(di_result_high)) * 100, 2)
    if all_down < 20 or len(result_arr) < 5:
        return None, None, None, None, None, None
    return today_d, len(result_arr), date_arr_hyp, down_times, vol2times, all_down


def get_all_stock_csv_path():
    for root, dirs, files in os.walk('stocks'):
        return [os.path.join(root, item) for item in files]


def run_down(today_date, N, p_sh_down_times):
    # D = True
    # today_date = run(D, bkd)
    dname = os.path.basename(__file__).split('.')[0]
    log_dir = f'result_{dname}'
    if not os.path.exists(log_dir):
        os.makedirs(log_dir)
    full_path_csv = f'{log_dir}/{today_date}_top_N{N}.csv'
    f_tk = open(full_path_csv, 'w', encoding='utf-8')
    f_tk.write(f'下跌次数,vol翻倍,累计跌幅,低点距离,连接,行业,名称,代码,当前价格,日期')
    df = pd.read_csv('cal_ops/all.csv')
    full_path_txt = f'result_a_recent_low_up/{today_date}_get_a_recent_low_up.txt'
    if os.path.exists(full_path_txt):
        os.remove(full_path_txt)
    logger.add(full_path_txt, format='{message}')
    cnt_number = 0
    for row in df.index:
        sn = StockNumber(df.loc[row])
        # logger.info(f'{today_date}, bkd={bkd}, N={N} {sn.name}')
        if 'ST' in sn.name:
            continue
        # if sn.name not in [
        #     '长虹华意',
        # ]:
        #     continue
        try:
            """
                elf.name = sn.name
                self.ts_code = sn.ts_code
                self.industry = sn.industry
                self.trade_date = df_row_data['trade_date']
                self.open = df_row_data['open']
                self.high = df_row_data['high']
                self.low = df_row_data['low']
                self.close = float(df_row_data['close'])
                self.pre_close = df_row_data['pre_close']
                self.change = df_row_data['change']
                self.pct_chg = float(df_row_data['pct_chg'])
                self.vol = df_row_data['vol']
                self.amount = df_row_data['amount']
            """
            today_d, max_len, date_arr_hyp, down_times, vol2times, all_up = get_3down_len(today_date, sn, N)
            if today_d is None and max_len is None:
                continue
            if down_times:
                continue
            w_msg = f'\n{down_times},{vol2times},{all_up},{max_len},{date_arr_hyp},{sn.industry},{sn.name},{sn.ts_code},{today_d.close},{today_date}'
            logger.info(f'{today_date}, bkd={bkd}, N={N} {sn.name}, {w_msg}')
            f_tk.write(w_msg)
            f_tk.flush()
            cnt_number += 1
        except Exception as e:
            print(e, traceback.format_exc())

    if os.path.exists(full_path_txt):
        os.remove(full_path_txt)

    f_tk.close()
    # True 从小到大， False 从大到小
    # 当前下跌次数最多，成交量翻倍最少，距离最大
    save_path_csv = full_path_csv.replace('.csv', f'_{cnt_number}.csv')
    sort_csv2(save_path_csv, full_path_csv, ['累计跌幅', '低点距离'], [False, False])
    # sdf = pandas.read_csv(full_path_csv)
    # email_datas = sdf.to_dict(orient='records')
    # if p_sh_down_times > 0:
    #     p_sh_down_str = f'SH【{p_sh_down_times}】连涨'
    # else:
    #     p_sh_down_str = f'SH【{p_sh_down_times}】连跌'
    #
    # msg_title = f'{os.path.basename(full_path_csv)[:8]}-{p_sh_down_str}-最近{N}跌'
    # send_email_html_down3.send_html(email_datas, msg_title, down_n)


if __name__ == '__main__':
    # 获取离最近N日顶，天数，行业，跌幅排序
    start_bkd = 0
    day_len = 3
    try:
        arguments = sys.argv[1:]
        if arguments:
            end_bkd = int(arguments[0])
            start_bkd = int(arguments[1]) if len(arguments) == 2 else start_bkd
        else:
            end_bkd = start_bkd + day_len
    except Exception as e:
        end_bkd = start_bkd + day_len
        logger.error(e)
    cal_date = [
        # '20250407',
        # '20250408',
        # '20250409',
        # '20250410',
        # '20250110',
        # '20250113',
        # '20250114',
        # '20250103',
        # '20250106',
        # '20250107',
        # '20240912',
        # '20240913',
        # '20240918',
        # '20240919',
        # '20240202',
        # '20240205',
        # '20240206',
        # '20231020',
        # '20231023',
        # '20231024',
    ]

    try:
        today_date = get_bkd_today()
        sh_dict, date_arr = get_sh_down_date()

        for bkd, d in enumerate(date_arr):
            if cal_date and d not in cal_date:
                continue
            if bkd < start_bkd:
                continue
            if bkd >= end_bkd:
                break
            sh_down_times = 0
            cnt = -1
            while 1:
                cnt += 1
                d_key = date_arr[bkd + cnt]
                sh_item = sh_dict.get(d_key)
                zdf = sh_item.get('涨跌幅')
                if sh_down_times > 0 and zdf < 0:
                    break
                if sh_down_times < 0 and zdf > 0:
                    break
                if zdf <= 0:
                    sh_down_times -= 1
                    continue
                if zdf > 0:
                    sh_down_times += 1
                    continue
            N = 10
            run_down(d, N, sh_down_times)
    except Exception as e:
        logger.error(e)
